home *** CD-ROM | disk | FTP | other *** search
/ Windows Game Programming for Dummies (2nd Edition) / WinGamProgFD.iso / pc / DirectX SDK / DXSDK / samples / Multimedia / VBSamples / Demos / AirHockey / modHelper.bas < prev    next >
Encoding:
BASIC Source File  |  2001-10-08  |  23.9 KB  |  640 lines

  1. Attribute VB_Name = "modAirHockey"
  2. Option Explicit
  3.  
  4. Public dx As New DirectX8
  5.  
  6. Public Type HockeyPlayerInfo
  7.     Score As Long 'Current score of this player
  8.     PlayerName As String ' The name of the player
  9.     Latency As Long 'Average latency (ping time) of this player
  10. End Type
  11.  
  12. 'Declare for timeGetTime
  13. Public Declare Function timeGetTime Lib "winmm.dll" () As Long
  14.  
  15. 'Registry constants (for saving and retreiving information)
  16. Public Const gsKeyName As String = "vbAirHockey"
  17. Public Const gsSubKey As String = "Defaults"
  18. Public Const gsSubKeyAudio As String = "Audio"
  19. Public Const gsSubKeyInput As String = "Input"
  20. Public Const gsSubKeyGraphics As String = "Graphics"
  21.  
  22. Public Const glMaxPuckSpeedConstant As Long = 10.23
  23.  
  24. 'The wall locations, use these for easier collision detection
  25. Public Const gnSideRightWallEdge As Single = -5
  26. Public Const gnSideLeftWallEdge As Single = 5
  27. Public Const gnNearWallEdge As Single = 9.92
  28. Public Const gnFarWallEdge As Single = -9.92
  29. 'We also need the dimensions for the 'scoring area' so we can tell when we score
  30. Public Const gnScoringEdgeLeft As Single = 1.35
  31. Public Const gnScoringEdgeRight As Single = -1.35
  32.  
  33. Public Const gnPuckScored As Single = 1.15
  34. 'Radius constants for the puck and paddle
  35. Public Const gnPuckRadius As Single = 0.46046
  36. Public Const gnPaddleRadius As Single = 0.6
  37. 'ComputerAI Maximum velocity
  38. Public Const gnComputerMaximumVelocity As Single = 0.43
  39. 'Winning score
  40. Public Const glDefaultWinningScore As Long = 7
  41.  
  42. 'We will ensure that we have at least a particular number of physics calculations per second
  43. 'We will lower frame rate to ensure we can calculate these physic calculations if necessary
  44. 'Number of physics calculations per second
  45. Public Const glNumPhysicCalcPerSec As Long = 100
  46. 'Ticks between physic calcs
  47. Public Const glNumTickForPhysicCalcs As Long = 1000 \ glNumPhysicCalcPerSec
  48.  
  49. 'Minimum delay before allowing another paddle hit
  50. Public Const glMinDelayPaddleHit = 100
  51. 'Delay time (ms) before 'helper' text appears
  52. Public Const glDefaultDelayTime As Long = 3000
  53. 'Delay time (ms) before 'helper' text disappears
  54. Public Const glDefaultDelayTimeGone As Long = 10000
  55. Public Const gnVelocityBoost As Single = 1.1
  56.  
  57. 'The objects that can appear in the scene
  58. Public goCamera As cCamera 'Doesn't really appear in the scene, but it does control what we see in the scene
  59. Public goPuck As cPuck 'The puck.  Pretty important
  60. Public goPaddle(1) As cPaddle 'There are two paddles
  61. Public goTable As cTable 'The table will never have a destination or a velocity, but we may need to move it's position
  62. Public goRoom As cRoom 'The room information
  63. Public goAudio As cAudio 'All of the audio information will be stored here
  64. Public goInput As cInput 'All of the input (mouse,keyboard, joystick,etc) will be stored here
  65. Public goFade As cFade 'The 'Fading' class
  66. 'Text variables
  67. Public goTextLittle As cText
  68. Public goTextBig As cText
  69. 'Main 'Select device' form
  70. Public goDev As frmSelectDevice
  71.  
  72. 'Which paddle am I controlling (Used mainly for multiplayer mode)
  73. Public glMyPaddleID As Long
  74. Public gfScored As Boolean 'Is the puck in the scored state
  75. Public gfMultiplayer As Boolean 'Is this a multiplayer game
  76. Public gfHost As Boolean 'Am I the host of this game?
  77. Public gfGameCanBeStarted As Boolean 'Can the game be started
  78. Public gPlayer(1) As HockeyPlayerInfo 'Current information of all the players
  79. Public gfRecentlyHitPaddle As Boolean 'Have we recently hit a paddle?
  80. 'Current time for all objects
  81. Public glTimeCompPaddle As Long
  82. 'Is the game over (ie, has someone won the game)
  83. Public gfGameOver As Boolean
  84. 'The user defined winning score
  85. Public glUserWinningScore As Long
  86. Public glPaddleCollideTime As Long
  87. 'We'll maintain a slight dampening factor for realism as the puck bounces off
  88. 'the wall
  89. Public gnVelocityDamp As Single
  90. 'Paddle mass
  91. Public gnPaddleMass As Single
  92. 'Time the puck was last scored
  93. Public glTimePuckScored As Long
  94. 'Time the game was over
  95. Public glTimeGameOver As Long
  96. 'Time the F1 help was displayed
  97. Public glTimeNoRoom As Long
  98. 'Is the system paused
  99. Public gfSystemPause As Boolean
  100.  
  101. Public gfDrawRoomText As Boolean
  102. Public glScreenWidth As Long
  103. Public glScreenHeight As Long
  104.  
  105. Public gfObjectsLoaded As Boolean
  106.  
  107. 'Extra misc vars
  108. Public gfWireFrame As Boolean
  109.  
  110. Public Sub MainGameLoop()
  111.     Dim lTime As Long
  112.     Dim lLastPhysicsTime As Long
  113.     
  114.     'Start the render loop
  115.     lTime = timeGetTime
  116.     Do While True
  117.         Do While Not gfSystemPause
  118.             'In each frame we need to do a few things
  119.             If (timeGetTime - lTime > 100) And (Not gfDrawRoomText) And (goRoom.DrawRoom) Then
  120.                 'We want to maintain a reasonable frame rate (10fps is on
  121.                 'the low end), so if we start taking too long between updates,
  122.                 'tell them they can get rid of the room
  123.                 gfDrawRoomText = True
  124.                 glTimeNoRoom = timeGetTime
  125.             End If
  126.             lTime = timeGetTime
  127.             'Check to see if the game is over
  128.             CheckGameOver
  129.             'We need to update any objects that are in the scene
  130.             UpdateObjects
  131.             'Get and handle any input
  132.             goInput.GetAndHandleInput goPaddle(glMyPaddleID), goPuck
  133.             If (Not gfScored) And (Not gfGameOver) Then
  134.                 'Next we need to check for any collisions that may have happened
  135.                 goPuck.CheckCollisions goPaddle, goAudio
  136.                 If Not gfMultiplayer Then 'Only on single player mode
  137.                     'Let the Computer AI do it's thing
  138.                     goPaddle(Abs(glMyPaddleID - 1)).DoComputerAI goPuck
  139.                 End If
  140.             End If
  141.             'We need to update the game state on the other machine
  142.             If gfMultiplayer Then
  143.                 UpdateNetworkSettings
  144.             Else
  145.                 If gfScored Then goPaddle(Abs(glMyPaddleID - 1)).UpdateTime
  146.             End If
  147.             'Only redraw the world if we're keeping up with our physic calculations
  148.             If timeGetTime - lLastPhysicsTime < glNumTickForPhysicCalcs Then
  149.                 'We should fade if necessary
  150.                 If goFade.AmFading Then goFade.UpdateFade goPuck, goPaddle, goTable, goRoom
  151.                 'Now we need to render the frame
  152.                 Render
  153.             End If
  154.             lLastPhysicsTime = timeGetTime
  155.             DoEvents
  156.         Loop
  157.         'Now give the CPU a chance
  158.         DoEvents
  159.     Loop
  160. End Sub
  161.  
  162. Public Sub LoadDefaultStartPositions()
  163.     'Our camera will start away from the table, and zoom in on it
  164.     With goCamera
  165.         .Position = vec3(0, 35, -40)
  166.         .LastPosition = .Position
  167.     End With
  168.     goCamera.SetCameraPosition 0, glMyPaddleID
  169.     'The puck's initial position should be on top of the table
  170.     With goPaddle(0)
  171.         .Position = vec3(0, 2.5, -6.8)
  172.         .LastPosition = .Position
  173.     End With
  174.     With goPaddle(1)
  175.         .Position = vec3(0, 2.5, 6.8)
  176.         .LastPosition = .Position
  177.     End With
  178.     With goTable
  179.         .Position = vec3(0, -5, 0)
  180.     End With
  181.     goPuck.DefaultStartPosition
  182.     
  183. End Sub
  184.  
  185. Public Sub UpdateObjects()
  186.     'We need a timer for each of the objects we're updating
  187.     Dim lCount As Long
  188.     
  189.     If gfMultiplayer And gfNoSendData Then 'Uh oh!  We've been disconnected sometime, no need to process anything
  190.         Exit Sub
  191.     End If
  192.     'Update the camera's position based on it's velocity
  193.     goCamera.UpdatePosition
  194.     'Update the puck's position
  195.     goPuck.UpdatePosition
  196. End Sub
  197.  
  198. Public Sub CheckGameOver()
  199.     Dim lCount As Long
  200.     
  201.     If gfGameOver Then Exit Sub
  202.     For lCount = 0 To 1
  203.         If gPlayer(lCount).Score >= glUserWinningScore Then
  204.             'Make sure we're leading the other player by 2 or more
  205.             If gPlayer(lCount).Score > gPlayer(Abs(lCount - 1)).Score + 1 Then
  206.                 gfGameOver = True
  207.                 glTimeGameOver = timeGetTime
  208.             End If
  209.         End If
  210.     Next
  211. End Sub
  212.  
  213. Public Sub ShowStartup()
  214.  
  215.     'Now 'zoom' in with our camera
  216.     Do While ((goCamera.Dest.Y <> goCamera.Position.Y) Or (goCamera.Dest.z <> goCamera.Position.z))
  217.         goCamera.UpdatePosition
  218.         Render
  219.         DoEvents
  220.     Loop
  221.     
  222. End Sub
  223.  
  224. Public Sub LoadObjects()
  225.         
  226.     If gfObjectsLoaded Then Exit Sub
  227.     'Initialize the objects
  228.     Set goPuck = New cPuck
  229.     Set goPaddle(0) = New cPaddle
  230.     goPaddle(0).PaddleID = 0
  231.     Set goPaddle(1) = New cPaddle
  232.     goPaddle(1).PaddleID = 1
  233.     If goCamera Is Nothing Then Set goCamera = New cCamera
  234.     Set goTable = New cTable
  235.     Set goRoom = New cRoom
  236.     
  237.     If goInput Is Nothing Then Set goInput = New cInput
  238.     If goAudio Is Nothing Then Set goAudio = New cAudio
  239.     If goFade Is Nothing Then Set goFade = New cFade
  240.     If goDev Is Nothing Then Set goDev = New frmSelectDevice
  241.     
  242.     D3DEnum_BuildAdapterList frmAir
  243.     
  244.     'Get any defaults from the registry we might need
  245.     goTable.DrawTable = GetSetting(gsKeyName, gsSubKey, "DrawTable", True)
  246.     goRoom.DrawRoom = GetSetting(gsKeyName, gsSubKey, "DrawRoom", True)
  247.     goRoom.barRoom = GetSetting(gsKeyName, gsSubKey, "RoomIsBarRoom", True)
  248.     
  249.     'Audio options
  250.     goAudio.PlayMusic = GetSetting(gsKeyName, gsSubKeyAudio, "UseBackgroundMusic", False)
  251.     goAudio.PlaySounds = GetSetting(gsKeyName, gsSubKeyAudio, "UseSound", True)
  252.     goAudio.MusicVolume = GetSetting(gsKeyName, gsSubKeyAudio, "MusicVolume", 0)
  253.     goAudio.SoundVolume = GetSetting(gsKeyName, gsSubKeyAudio, "SoundVolume", 0)
  254.     'Input options
  255.     goInput.UseMouse = GetSetting(gsKeyName, gsSubKeyInput, "UseMouse", True)
  256.     goInput.UseKeyboard = GetSetting(gsKeyName, gsSubKeyInput, "UseKeyboard", True)
  257.     goInput.UseJoystick = GetSetting(gsKeyName, gsSubKeyInput, "UseJoystick", False)
  258.     goInput.JoystickGuid = GetSetting(gsKeyName, gsSubKeyInput, "JoystickGuid", vbNullString)
  259.     goInput.JoystickSensitivity = GetSetting(gsKeyName, gsSubKeyInput, "JoystickSensitivity", 0.00025)
  260.     goInput.MouseSensitivity = GetSetting(gsKeyName, gsSubKeyInput, "MouseSensitivity", 0.02)
  261.     goInput.KeyboardSensitivity = GetSetting(gsKeyName, gsSubKeyInput, "KeyboardSensitivity", 0.002)
  262.     'D3D options
  263.     goDev.Windowed = GetSetting(gsKeyName, gsSubKeyGraphics, "Windowed", True)
  264.     goDev.Adapter = GetSetting(gsKeyName, gsSubKeyGraphics, "AdapterID", 0)
  265.     goDev.Mode = GetSetting(gsKeyName, gsSubKeyGraphics, "Mode", 0)
  266.     
  267.     gfObjectsLoaded = True
  268.     
  269. End Sub
  270.  
  271. Public Sub PauseSystem(ByVal fPause As Boolean)
  272.     gfSystemPause = fPause
  273.     If Not fPause Then
  274.         glTimeCompPaddle = timeGetTime
  275.     End If
  276.     If Not (goPuck Is Nothing) Then
  277.         goPuck.PauseSystem fPause
  278.     End If
  279. End Sub
  280.  
  281. Public Sub Cleanup(Optional fFinalCleanup As Boolean = False, Optional fOnlyD3D As Boolean = False)
  282.     
  283.     'Getting rid of the objects will clean up the internal objects
  284.     If fFinalCleanup Then
  285.         Set goPuck = Nothing
  286.         Set goPaddle(0) = Nothing
  287.         Set goPaddle(1) = Nothing
  288.         Set goTable = Nothing
  289.         Set goRoom = Nothing
  290.         Set goTextBig = Nothing
  291.         Set goTextLittle = Nothing
  292.         If Not fOnlyD3D Then
  293.             Set goInput = Nothing
  294.             Set goAudio = Nothing
  295.             Set goFade = Nothing
  296.             Set goDev = Nothing
  297.         End If
  298.         gfObjectsLoaded = False
  299.     Else
  300.         goPuck.CleanupFrame
  301.         goPaddle(0).CleanupFrame
  302.         goPaddle(1).CleanupFrame
  303.         goTable.CleanupFrame
  304.         goRoom.CleanupFrame
  305.     End If
  306. End Sub
  307.  
  308. Public Sub InitGeometry()
  309.         
  310.     LoadObjects
  311.     'First set up the media
  312.     D3DUtil_SetMediaPath AddDirSep(App.path) & "models\"
  313.     goRoom.Init g_mediaPath, "room.x", "lobby_skybox.x"
  314.     frmAir.IncreaseProgressBar
  315.     goPaddle(1).Init g_mediaPath, "paddle.x"
  316.     frmAir.IncreaseProgressBar
  317.     goPaddle(0).Init g_mediaPath, "paddle.x"
  318.     frmAir.IncreaseProgressBar
  319.     goPuck.Init g_mediaPath, "puck.x"
  320.     frmAir.IncreaseProgressBar
  321.     goTable.Init g_mediaPath, "table.x"
  322.     frmAir.IncreaseProgressBar
  323.     
  324. End Sub
  325.  
  326. Public Sub Render()
  327.  
  328.     Dim lCount As Long
  329.     
  330.     On Error Resume Next
  331.     If gfSystemPause Then Exit Sub
  332.     If g_dev Is Nothing Then Exit Sub
  333.  
  334.         ' Clear the backbuffer to a black color
  335.     If gfMultiplayer And gfNoSendData Then 'Uh oh!  We've been disconnected sometime, notify the user
  336.         D3DUtil_ClearAll &HFF0000FF 'Clear with a blue background
  337.     Else
  338.         D3DUtil_ClearAll 0
  339.         
  340.         ' Setup the view and projection matrices
  341.         SetupMatrices
  342.         
  343.         ' Begin the scene
  344.         g_dev.BeginScene
  345.         
  346.         'Draw everything in either a solid fillmode, or wireframe
  347.         If gfWireFrame Then
  348.            g_dev.SetRenderState D3DRS_FILLMODE, D3DFILL_WIREFRAME
  349.         Else
  350.            g_dev.SetRenderState D3DRS_FILLMODE, D3DFILL_SOLID
  351.         End If
  352.        
  353.         If goFade.AmFading Then
  354.             g_dev.SetRenderState D3DRS_ALPHABLENDENABLE, 1  'TRUE
  355.             g_dev.SetRenderState D3DRS_SRCBLEND, D3DBLEND_SRCALPHA
  356.             g_dev.SetRenderState D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA
  357.         End If
  358.        
  359.         'Render the room
  360.         goRoom.Render g_dev
  361.        
  362.         'Render the table
  363.         goTable.Render g_dev
  364.         
  365.         'Now Paddle (0)
  366.         goPaddle(0).Render g_dev
  367.         
  368.         'Now Paddle (1)
  369.         goPaddle(1).Render g_dev
  370.         
  371.         'And finally the puck
  372.         goPuck.Render g_dev
  373.         'Now lets draw whatever text we need
  374.     End If
  375.     
  376.     'We can draw text (don't draw text if we're currently fading)
  377.     If Not goFade.AmFading Then
  378.         goTextLittle.BeginText
  379.         If gfGameCanBeStarted Then
  380.             'If the game can be started, then draw the scores at the top of the screen
  381.             If gfMultiplayer Then
  382.                 If glMyPaddleID = 0 Then
  383.                     goTextLittle.DrawText gsUserName & ":" & gPlayer(0).Score, 10, 5, &HFFFFFF00
  384.                 Else
  385.                     goTextLittle.DrawText "Opponent:" & gPlayer(0).Score, 10, 5, &HFFFFFFFF
  386.                 End If
  387.                 If glMyPaddleID = 1 Then
  388.                     goTextLittle.DrawText gsUserName & ":" & gPlayer(1).Score, glScreenWidth - 75, 5, &HFFFFFF00
  389.                 Else
  390.                     goTextLittle.DrawText "Opponent:" & gPlayer(1).Score, glScreenWidth - 75, 5, &HFFFFFFFF
  391.                 End If
  392.             Else
  393.                 goTextLittle.DrawText "Player:" & gPlayer(0).Score, 10, 5, &HFFFFFF00
  394.                 goTextLittle.DrawText "Computer:" & gPlayer(1).Score, glScreenWidth - 75, 5, &HFFFFFFFF
  395.             End If
  396.         Else
  397.             'The game can't be started yet (only in multiplayer)  Let the host know
  398.             goTextLittle.DrawText "Waiting for the game to be started...", (glScreenWidth / 2) - 50, 5, &HFFFFFFFF
  399.         End If
  400.         'Here is a little helper text letting the user know to press Space
  401.         'to launch the puck (will show up after 3 seconds, and stay on for 10 seconds)
  402.         If (timeGetTime - glTimePuckScored > glDefaultDelayTime) And gfScored And Not gfGameOver And ((timeGetTime - glTimePuckScored < glDefaultDelayTimeGone + glDefaultDelayTime)) Then
  403.             goPuck.DefaultStartPosition
  404.             goPuck.Spinning = True
  405.             goTextLittle.DrawText "Press <Space> to launch puck...", (glScreenWidth / 2) - 50, 25, &HFF0000FF
  406.         End If
  407.         
  408.         'Here is a little helper text letting the user know to press F1
  409.         'to turn of the room (will show up after 3 seconds, and stay on for 10 seconds)
  410.         If (gfDrawRoomText And goRoom.DrawRoom) And (timeGetTime - glTimeNoRoom < glDefaultDelayTimeGone) Then
  411.             goTextLittle.DrawText "You can press F1 to turn off the drawing " & vbCrLf & " of the room, which will increase performance.", -15, glScreenHeight - 50, &HFFFF00FF
  412.         End If
  413.         If gfGameOver And ((timeGetTime - glTimeGameOver) > glDefaultDelayTime) And ((timeGetTime - glTimeGameOver < glDefaultDelayTimeGone + glDefaultDelayTime)) Then
  414.             goTextLittle.DrawText "Press F3 to restart...", (glScreenWidth / 2) - 50, 25, &HFF0000FF
  415.         End If
  416.         goTextLittle.EndText
  417.         goTextBig.BeginText
  418.         If gfGameOver Then
  419.             If gfMultiplayer Then
  420.                 If gPlayer(glMyPaddleID).Score > gPlayer(Abs(glMyPaddleID - 1)).Score Then
  421.                     goTextBig.DrawText "Game over!!" & vbCrLf & "You win!!", (glScreenWidth / 2) - (glScreenWidth / 4), (glScreenHeight / 2) - (glScreenHeight / 4), &HFFDD11AA
  422.                 Else
  423.                     goTextBig.DrawText "Game over!!" & vbCrLf & "You lose!!", (glScreenWidth / 2) - (glScreenWidth / 4), (glScreenHeight / 2) - (glScreenHeight / 4), &HFFDD11AA
  424.                 End If
  425.             Else
  426.                 If gPlayer(0).Score > gPlayer(1).Score Then
  427.                     goTextBig.DrawText "Game over!!" & vbCrLf & "You win!!", (glScreenWidth / 2) - (glScreenWidth / 4), (glScreenHeight / 2) - (glScreenHeight / 4), &HFFDD11AA
  428.                 Else
  429.                     goTextBig.DrawText "Game over!!" & vbCrLf & "You lose!!", (glScreenWidth / 2) - (glScreenWidth / 4), (glScreenHeight / 2) - (glScreenHeight / 4), &HFFDD11AA
  430.                 End If
  431.             End If
  432.         End If
  433.         If gfMultiplayer And gfNoSendData Then 'Uh oh!  We've been disconnected sometime, notify the user
  434.             goTextBig.DrawText "The connection with the other" & vbCrLf & "system was lost.", 5, (glScreenHeight / 2) - (glScreenHeight / 4), &HFFFFFF00
  435.             'This message isn't on a timer to go away
  436.         End If
  437.         goTextBig.EndText
  438.     End If
  439.     ' End the scene
  440.     g_dev.EndScene
  441.     ' Present the backbuffer contents to the front buffer (screen)
  442.     D3DUtil_PresentAll 0
  443.     
  444. End Sub
  445.  
  446. Public Sub SetupMatrices()
  447.     
  448.     Dim matView As D3DMATRIX
  449.     Dim matProj As D3DMATRIX
  450.         
  451.     D3DXMatrixLookAtLH matView, goCamera.Position, vec3(0#, 0#, 0#), vec3(0#, 1#, 0#)
  452.     g_dev.SetTransform D3DTS_VIEW, matView
  453.     
  454.     D3DXMatrixPerspectiveFovLH matProj, g_pi / 4, 1, 1, 110
  455.     g_dev.SetTransform D3DTS_PROJECTION, matProj
  456.  
  457. End Sub
  458.  
  459. Public Sub RestoreDeviceObjects()
  460.  
  461.     ' Set miscellaneous render states
  462.     With g_dev
  463.         ' Set world transform
  464.         Dim matWorld As D3DMATRIX
  465.         D3DXMatrixIdentity matWorld
  466.         .SetTransform D3DTS_WORLD, matWorld
  467.         
  468.         .SetTextureStageState 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE
  469.         .SetTextureStageState 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1
  470.         .SetTextureStageState 0, D3DTSS_ALPHAARG1, D3DTA_DIFFUSE
  471.         .SetTextureStageState 0, D3DTSS_MINFILTER, D3DTEXF_LINEAR
  472.         .SetTextureStageState 0, D3DTSS_MAGFILTER, D3DTEXF_LINEAR
  473.  
  474.         ' Set default render states
  475.         .SetRenderState D3DRS_ZENABLE, 1 'True
  476.  
  477.     End With
  478.     
  479.     Set goTextBig = Nothing
  480.     Set goTextLittle = Nothing
  481.     
  482.     'Now create a new text object
  483.     Set goTextLittle = New cText
  484.     goTextLittle.InitText g_d3dx, g_dev, "Times New Roman", 8, True
  485.     Set goTextBig = New cText
  486.     goTextBig.InitText g_d3dx, g_dev, "Times New Roman", 18, True
  487.     
  488. End Sub
  489.  
  490. Public Sub InitDefaultLights(ByVal lNumLights As Long)
  491.     With g_dev
  492.         ' Set ambient light
  493.         .SetRenderState D3DRS_AMBIENT, &HFFFFFFFF
  494.         If lNumLights < 3 Then Exit Sub 'Nothing to do
  495.         
  496.         ' Set ambient light
  497.         'We will slowly lower the ambient light as each new light gets added
  498.         .SetRenderState D3DRS_AMBIENT, &HFFBBBBBB
  499.         ' Turn on lighting
  500.         .SetRenderState D3DRS_LIGHTING, 1
  501.         
  502.         'Turn on two lights one on each end of the table
  503.         Dim light As D3DLIGHT8
  504.         
  505.         If lNumLights > 0 Then
  506.             With light
  507.                 .Type = D3DLIGHT_DIRECTIONAL
  508.                 .diffuse.r = 1
  509.                 .diffuse.g = 1
  510.                 .diffuse.b = 1
  511.                 .Direction.X = 0
  512.                 .Direction.Y = -10
  513.                 .Direction.z = 0
  514.                 .Range = 1.84467435229094E+19 'User defined.
  515.                 .Position.X = 0
  516.                 .Position.Y = 3
  517.                 .Position.z = 0
  518.             End With
  519.     
  520.             .SetLight 0, light                   'let d3d know about the light
  521.             .LightEnable 0, 1                    'turn it on
  522.         End If
  523.         
  524.         
  525.         If lNumLights > 1 Then
  526.             .SetRenderState D3DRS_AMBIENT, &HFFAAAAAA
  527.             'Now turn on the second light if we can
  528.             With light
  529.                 .Type = D3DLIGHT_DIRECTIONAL
  530.                 .Direction.X = 5
  531.                 .Direction.Y = -3
  532.                 .Direction.z = -5
  533.                 .Position.X = -5
  534.                 .Position.Y = 3
  535.                 .Position.z = 5
  536.             End With
  537.     
  538.             .SetLight 1, light                   'let d3d know about the light
  539.             .LightEnable 1, 1                    'turn it on
  540.         End If
  541.  
  542.         
  543.         If lNumLights > 3 Then
  544.             .SetRenderState D3DRS_AMBIENT, 0
  545.             'Now turn on the third light if we can
  546.             With light
  547.                 .Type = D3DLIGHT_DIRECTIONAL
  548.                 .Direction.X = -5
  549.                 .Direction.Y = 3
  550.                 .Direction.z = 5
  551.                 .Position.X = 5
  552.                 .Position.Y = -3
  553.                 .Position.z = -5
  554.             End With
  555.     
  556.             .SetLight 2, light                   'let d3d know about the light
  557.             .LightEnable 2, 1                    'turn it on
  558.         End If
  559.     End With
  560. End Sub
  561.  
  562. Public Sub SaveOrRestoreObjectSettings(ByVal fSave As Boolean)
  563.     'Puck
  564.     Static LastPuckPosition As D3DVECTOR
  565.     Static PuckPosition As D3DVECTOR
  566.     Static MaxPuckVel As Single
  567.     Static PuckSpinning As Boolean
  568.     Static PuckVelocity As D3DVECTOR
  569.     
  570.     If fSave Then
  571.         LastPuckPosition = goPuck.LastPosition
  572.         MaxPuckVel = goPuck.MaximumPuckVelocity
  573.         PuckPosition = goPuck.Position
  574.         PuckSpinning = goPuck.Spinning
  575.         PuckVelocity = goPuck.Velocity
  576.     Else
  577.         goPuck.LastPosition = LastPuckPosition
  578.         goPuck.MaximumPuckVelocity = MaxPuckVel
  579.         goPuck.Position = PuckPosition
  580.         goPuck.Spinning = PuckSpinning
  581.         goPuck.Velocity = PuckVelocity
  582.     End If
  583.     
  584.     'paddles
  585.     Static LastPaddlePosition(1) As D3DVECTOR
  586.     Static LastPaddleVelTick(1) As Long
  587.     Static PaddleID(1) As Long
  588.     Static PaddlePosition(1) As D3DVECTOR
  589.     Static PaddleTrans(1) As Boolean
  590.     Static PaddleVelocity(1) As D3DVECTOR
  591.     
  592.     Dim i As Integer
  593.     If fSave Then
  594.         For i = 0 To 1
  595.             LastPaddlePosition(i) = goPaddle(i).LastPosition
  596.             LastPaddleVelTick(i) = goPaddle(i).LastVelocityTick
  597.             PaddleID(i) = goPaddle(i).PaddleID
  598.             PaddlePosition(i) = goPaddle(i).Position
  599.             PaddleTrans(i) = goPaddle(i).Transparent
  600.             PaddleVelocity(i) = goPaddle(i).Velocity
  601.         Next
  602.     Else
  603.         For i = 0 To 1
  604.             goPaddle(i).LastPosition = LastPaddlePosition(i)
  605.             goPaddle(i).LastVelocityTick = LastPaddleVelTick(i)
  606.             goPaddle(i).PaddleID = PaddleID(i)
  607.             goPaddle(i).Position = PaddlePosition(i)
  608.             goPaddle(i).Transparent = PaddleTrans(i)
  609.             goPaddle(i).Velocity = PaddleVelocity(i)
  610.         Next
  611.     End If
  612.     
  613.     'Room
  614.     Static barRoom As Boolean
  615.     Static DrawRoom As Boolean
  616.     If fSave Then
  617.         barRoom = goRoom.barRoom
  618.         DrawRoom = goRoom.DrawRoom
  619.     Else
  620.         goRoom.barRoom = barRoom
  621.         goRoom.DrawRoom = DrawRoom
  622.     End If
  623.     
  624.     'Table
  625.     Static DrawTable As Boolean
  626.     Static TablePosition As D3DVECTOR
  627.     Static TableTrans As Boolean
  628.     
  629.     If fSave Then
  630.         DrawTable = goTable.DrawTable
  631.         TablePosition = goTable.Position
  632.         TableTrans = goTable.Transparent
  633.     Else
  634.         goTable.DrawTable = DrawTable
  635.         goTable.Position = TablePosition
  636.         goTable.Transparent = TableTrans
  637.     End If
  638.     
  639. End Sub
  640.